网页自动化 您所在的位置:网站首页 vba WebBrowser下载图片 网页自动化

网页自动化

2024-07-10 13:47| 来源: 网络整理| 查看: 265

 

 

VBA自动化网页的多种方式

其实并不知道有多少种方式,下面随便罗列了一些:

1.WebBrower方式

2.InternetExplorer.Application方式,需要引入接口:'在VBA编辑器窗口依次点击 工具==引用 勾选Microsoft  Internet  Controls 确定,再运行,OK!

3.XMLHTTP 学习资料如下:链接已死!

4.

InternetExplorer.Application方式

创建InternetExplorer.Application

   Set ie = CreateObject("internetexplorer.application")

   ie.Visible = True

   ie.Navigate "http://www.baidu.com/"

连接InternetExplorer.Application

如果能直接链接到已经打开至特定网页的浏览器,这就可以省略掉许多如登录等非重复工作的编码工作,但愿如此。

或许可使用此函数GetObject实现(似乎实现不了)

set ie = GetObject(“”, “InternetExplorer.Application”)

这条语句并不会链接到已经打开的IE上,而是重新打开一个IE,更坑的是,它还是隐藏的,是个空白页。

2.Win32 API方式Function FindWin(ByVal strRef As String) As Object    '找寻已打开的、以strRef为开头网址的网页    Dim objWin As Object    For Each objWin In CreateObject("Shell.Application").Windows        Do While objWin.readyState 4 Or objWin.Busy            DoEvents        Loop        If LCase(TypeName(objWin.document)) = "htmldocument" Then            If objWin.LocationURL Like strRef & "*" Then                Set FindWin = objWin                Exit For            End If        End If    Next    Set objWin = NothingEnd Function

3.未知原理方式,简洁有效

'引用:'Library SHDocVw'    C:\WINDOWS\system32\SHDOCVW.dll'    Microsoft Internet ControlsSub Inputall()    Dim mShellwindows As New ShellWindows    Dim IE As InternetExplorer       For Each IE In mShellwindows        If IE.LocationURL Like "http://mail.126.com*" Then Exit For    Next       With IE.document        .all("USER").Value = "ABCD"        .all("PASSWORD").Value = 1234        .all("enter.x").Click        Do While IE.Busy            DoEvents        Loop    End WithEnd Sub

注意的是,此种情况下IE不具有焦点,可以用如下语句将其设为活动窗口:

SetForegroundWindow(IE.HWND)

此时由于IE为活动窗口,将其上的控件设为具有焦点后,则可接受按键信息

item.focus

SendKeys "{enter}"

点连接出现新选项卡的处理

InternetExplorer.Application中没有选择选项卡的功能,或许可以用GetObject功能来获得新选项卡中的文档?未知。

另一个方式:在点击前,改变 t1 + 5 '需要时间触发网页上的onblur函数

       DoEvents

Loop

方法二:

在VBA中使用Sleep函数,需要添加:

Private Declare Sub Sleep Lib "kernel32" (ByValdwMilliseconds As Long)

'   Sleep (53000)

方法三:

'如下,可以暫停10秒.实现类似于Sleep函数的功能

'newHour = Hour(Now())

'newMinute = Minute(Now())

'newSecond = Second(Now()) + 10

'waitTime = TimeSerial(newHour, newMinute, newSecond)

'Application.Wait waitTime

处理Alert等弹出式窗口

方法一:

利用事件驱动方式将相关函数预设为空函数。待证实

DimWithEvents ie As SHDocVw.InternetExplorer 

'Private Subie_NavigateComplete2(ByVal pDisp As Object, URL As Variant)

'pDisp.Document.parentWindow.execScript "window.alert=null;"

'pDisp.Document.parentWindow.execScript "window.confirm=null;"

'pDisp.Document.parentWindow.execScript "window.showModalDialog=null;"

'pDisp.Document.parentWindow.execScript "window.open=null;"

'End Sub

'

方法二:

原理和上面的相似,但不需要用到事件驱动方式。待证实,可能不适合动态产生的信息窗口

   Set objscr = .Document.createElement_x("script") '创建一个脚本元素

   objscr.Text = "window.confirm=function(x){return true;};" 'true是点击“确定”,false是点击“取消”

.Document.body.appendChild objscr '将脚本元素添加到body里

.document.getElementByIdx_x("submit").Click ‘会产生弹出窗口的执行语句

方法三:

感觉此方法与InternetExplorer.Application不协调,但是我唯一成功使用过的方法。这种方法应该算是软件自动化的一个基础,例如编写游戏外挂。

找到弹出窗口的窗口句柄,并向其上的按钮发送单击事件从而关闭窗口。已证实可用,可应付动态产生的信息窗口

MicrosoftSpy++:工具,用于取得窗口类名、名称,控件类名、名称和WM信息等。

FindWindow:Win32 API函数,功能为取得窗口句柄

FindWindowEx: Win32 API函数,功能为取得窗口中控件的句柄

SendMessage: Win32 API函数,发送WM信息

声明部分:

Private Declare PtrSafe Function FindWindowEx Lib"user32" Alias "FindWindowExA" (ByVal hWnd1 As Long, ByValhWnd2 As Long, ByVal lpsz1 As String, ByVal lpsz2 As Any) As Long 'API抓窗口函数

Private Declare PtrSafe Function GetWindowText Lib"user32" Alias "GetWindowTextA" (ByVal hwnd As Long, ByVallpString As String, ByVal cch As Long) As Long 'api取窗口文本函数

Private Declare PtrSafe Function FindWindow Lib"user32" Alias "FindWindowA" (ByVal lpClassName As String,ByVal lpWindowName As String) As Long

Private Declare PtrSafe Function SendMessage Lib"user32" Alias "SendMessageA" (ByVal hwnd As Long, ByValwMsg As Long, ByVal wParam As Long, lParam As Any) As Long

Public Const WM_LBUTTONDOWN = &H201

Public Const WM_LBUTTONUP = &H202

Public Const MK_LBUTTON = &H1

执行语句部分:

           Do Until FindWindow("#32770", "来自网页的消息") >0

               DoEvents

           Loop

           hwd = FindWindow("#32770", "来自网页的消息")  '网页对话框的句柄

           Do Until FindWindowEx(hwd, 0, "Button", "确定") > 0

               DoEvents

           Loop

           hwd_child = FindWindowEx(hwd, 0, "Button", "确定") '保存按钮的句柄

           SendMessage hwd_child, BM_CLICK, 0, 0 '发送鼠标单击       ‘这一句似乎不能起作用,下面两句可以完成点击功能

           SendMessage hwd_child, WM_LBUTTONDOWN, 0, ByVal0              '点击“确定”按钮(按下左键)

           SendMessage hwd_child, WM_LBUTTONUP, 0, ByVal0                '点击“确定”按钮(松开左键)

注意:由于网页和程序是异步的,所以要防止弹出窗口还没准备好,而执行语句已经到达,故上面层层检查弹出窗口是否已经准备好,最好在发送WM信息前再延时1秒,已防意外。

动态加载页面的处理

本条内容待证实。

网页脚本中,加入的js类的代码,该代码的作用是动态加载网页内容,这里的动态是指,当鼠标或者滚动条滚动到此处时,才会自动加载网页内容,否则网页始终不加载,所以程序就陷入了无限循环,这个解决方法就是模拟滚动条滚动到需要加载内容的区域。

这涉及到两个内容:

第一个网页元素在浏览器页面中的定位方法;

元素对象相对于目前浏览器顶部位置的像素距离:object.getBoundingClientRect().top

元素对象相对于目前浏览器左侧位置的像素距离:object.getBoundingClientRect().left

第二个滚动条控制方法;

     Document.parentWindow.scrollBy X,Y(一般x为0,Y为top值)

所以,完整答案为:

用框架里面或者链接加载完毕后里面的代码,这个代码要能够跟主页面代码有所区别,就是说主页面里面没有的代码,然后通过在主页面代码里面查找框架或链接里面独特代码是否存在的形式,来完成页面是否加载的判断,具体代码为:

Do WhileInStr(主页面代码, "框架某一独特代码")



【本文地址】

公司简介

联系我们

今日新闻

    推荐新闻

    专题文章
      CopyRight 2018-2019 实验室设备网 版权所有